#include <base_definition.h>
#include <elf.h>
#include <config.h>
#include <page.h>
#include <boot_ld.h>
#include <misc.h>

noreturn void PM_Main(void)
{
    Elf64_Ehdr *ehdr = (Elf64_Ehdr *)KERNEL_BASE;

    // 检查ELF标识与头信息
    char *ident = IDENT_STR;
    char *s = (char *)ehdr, *d = ident;
    for (int i = 0; i < IDENT_LEN; i++, s++, d++)
    {
        if (*s != *d)
            die();
    }

    // 遍历程序头
    Elf64_Phdr *phdr = (Elf64_Phdr *)((ptr)ehdr->e_phoff + (ptr)ehdr);
    u32 phdrnum = ehdr->e_phnum;
    for (int i = 0; i < phdrnum; i++)
    {
        // 加载所有PT_LOAD段
        if (phdr->p_type == PT_LOAD)
        {
            memcpy((ptr)phdr->p_offset + (ptr)ehdr, phdr->p_vaddr - KERNEL_VMSTART + KERNEL_PMSTART, (u32)phdr->p_memsz);
        }
    }

    asm volatile("jmp lmjump" ::"A"(ehdr->e_entry));
    die();
}
